// file:arch/x86/include/arch/gate.h
// autor:jiangxinpeng
// time:2021.1.27
// copyright:(C) 2020-2050 by jiangxinpeng,All right are reserved.

#ifndef X86_GATE_H
#define X86_GATE_H

#include <arch/segment.h>
#include <lib/type.h>
#include <arch/pic.h>
#include <arch/page.h>

#define IDT_BASE 0x8F0800                     // IDT base address
#define IDT_VBASE (PAGE_HIGH_BASE + IDT_BASE) // IDT virtual address
#define IDT_LIMIT 0x7ff

// max interrupt count
#define INT_MAX 255

#define GATE_INT SEG_TYPE_INTGATE
#define GATE_TASK SEG_TYPE_TASKGATE
#define GATE_TRAP SEG_TYPE_TRAPGATE
#define GATE_CALL SEG_TYPE_CALLGATE

#define GATE_DPL0 0
#define GATE_DPL1 1
#define GATE_DPL2 2
#define GATE_DPL3 3

// syscall number
#define SYSCALL_NUM 0x40

#pragma pack(push, 1)
typedef struct
{
    uint16_t off_low;
    uint16_t sel;
    uint8_t datacount;
    uint8_t attr;
    uint16_t off_high;
} gate_t;
#pragma pack(pop)

extern volatile gate_t *idt;

extern void ExceptionEntry0x00();
extern void ExceptionEntry0x01();
extern void ExceptionEntry0x02();
extern void ExceptionEntry0x03();
extern void ExceptionEntry0x04();
extern void ExceptionEntry0x05();
extern void ExceptionEntry0x06();
extern void ExceptionEntry0x07();
extern void ExceptionEntry0x08();
extern void ExceptionEntry0x09();
extern void ExceptionEntry0x0a();
extern void ExceptionEntry0x0b();
extern void ExceptionEntry0x0c();
extern void ExceptionEntry0x0d();
extern void ExceptionEntry0x0e();
extern void ExceptionEntry0x0f();
extern void ExceptionEntry0x10();
extern void ExceptionEntry0x11();
extern void ExceptionEntry0x12();
extern void ExceptionEntry0x13();
extern void ExceptionEntry0x14();
extern void ExceptionEntry0x15();
extern void ExceptionEntry0x16();
extern void ExceptionEntry0x17();
extern void ExceptionEntry0x18();
extern void ExceptionEntry0x19();
extern void ExceptionEntry0x1a();
extern void ExceptionEntry0x1b();
extern void ExceptionEntry0x1c();
extern void ExceptionEntry0x1d();
extern void ExceptionEntry0x1e();
extern void ExceptionEntry0x1f();
extern void IrqEntry0x20();
extern void IrqEntry0x21();
extern void IrqEntry0x22();
extern void IrqEntry0x23();
extern void IrqEntry0x24();
extern void IrqEntry0x25();
extern void IrqEntry0x26();
extern void IrqEntry0x27();
extern void IrqEntry0x28();
extern void IrqEntry0x29();
extern void IrqEntry0x2a();
extern void IrqEntry0x2b();
extern void IrqEntry0x2c();
extern void IrqEntry0x2d();
extern void IrqEntry0x2e();
extern void IrqEntry0x2f();
extern void IrqEntry0x30();

extern void SysCallHandler();

extern void APICTimerHandler();
extern void APICErrHandler();

void InterruptGateInit();
void GateDescriptInit();
gate_t __attribute__((optimize("02"))) MakeGateDescript(uint16_t sel, uint32_t offset, uint8_t attri);
void __attribute__((optimize("O2"))) SetGateDescript(uint8_t vec, void *handler);
#endif